package main

import (
	"ai-gateway/common"
	"ai-gateway/config"
	_ "ai-gateway/config"
	"ai-gateway/db"
	"ai-gateway/proto"
	"context"
	"fmt"
	"net"

	"google.golang.org/grpc"
)

type RouteServer struct {
	proto.UnimplementedRouteServiceServer
}

func (s *RouteServer) SelectProvider(ctx context.Context, req *proto.AIRequest) (*proto.RouteResponse, error) {
	scenario := req.Scenario
	// 查询时包含数据库中的性能评分字段
	var policies []struct {
		Provider         string  `db:"preferred_provider"`
		TokenPrice       float64 `db:"token_price"`
		PerformanceScore float64 `db:"performance_score"` // 从数据库读取性能分（1-10分）
	}
	err := db.DB.Select(&policies, `
		SELECT preferred_provider, token_price, performance_score
		FROM route_policies 
		WHERE business_system = ? AND scenario = ?
	`, req.BusinessSystem, scenario)

	// 处理查询结果
	if err != nil || len(policies) == 0 {
		common.Logger.Warn().Err(err).Str("scenario", scenario).Msg("路由策略查询失败或无数据，使用默认策略")
		return &proto.RouteResponse{
			Provider:   "alibaba",
			TokenPrice: 0.002,
		}, nil
	}
	// 计算综合得分（性能50%+成本50%）
	bestProvider := policies[0]
	bestScore := 0.0
	maxPrice := 0.15 // 价格上限，用于归一化成本得分
	for _, policy := range policies {
		// 性能得分：直接使用数据库中的评分（1-10分）
		perfScore := policy.PerformanceScore
		// 确保性能分在有效范围内（避免数据库配置错误）
		if perfScore < 1 || perfScore > 10 {
			common.Logger.Warn().Str("provider", policy.Provider).Float64("score", perfScore).Msg("性能评分超出1-10范围，使用默认值7")
			perfScore = 7.0
		}
		// 成本得分：归一化为0-10分
		priceScore := (maxPrice - policy.TokenPrice) / maxPrice * 10
		// 避免价格异常导致的负分（如价格超过maxPrice时按0分处理）
		if priceScore < 0 {
			priceScore = 0
		}
		// 综合得分计算，各占50%权重
		totalScore := perfScore*0.5 + priceScore*0.5

		// 更新最佳选择
		if totalScore > bestScore {
			bestScore = totalScore
			bestProvider = policy
		}
	}

	common.Logger.Info().
		Str("business_system", req.BusinessSystem).
		Str("scenario", scenario).
		Str("provider", bestProvider.Provider).
		Float64("token_price", bestProvider.TokenPrice).
		Float64("performance_score", bestProvider.PerformanceScore).
		Float64("total_score", bestScore).
		Msg("基于数据库性能评分和成本的最优路由选择")

	return &proto.RouteResponse{
		Provider:   bestProvider.Provider,
		TokenPrice: float32(bestProvider.TokenPrice),
	}, nil
}

func main() {
	common.InitLogger("route-service")
	if err := db.InitDB(); err != nil {
		common.Logger.Fatal().Err(err).Msg("数据库初始化失败")
	}

	lis, err := net.Listen("tcp", fmt.Sprintf("%s%d", ":", config.Config.RouteServicePort))
	if err != nil {
		common.Logger.Fatal().Err(err).Msg("监听端口失败")
	}

	s := grpc.NewServer()
	proto.RegisterRouteServiceServer(s, &RouteServer{})
	common.Logger.Info().Msg("Route Service 启动: :8082")

	if err := s.Serve(lis); err != nil {
		common.Logger.Fatal().Err(err).Msg("服务启动失败")
	}
}
